strspn関数、strcspn関数は、文字列の先頭から文字のセットに含まれる文字を検索し、先頭から該当する文字までの文字数(長さ)を返します。2つの関数の相違は、次のとおりです。

  1. strspn関数は、文字セットに含まれる文字の部分を探して、その文字までの文字数を返します。
  2. strcspn関数は、文字セットに含まれない文字の部分を探して、その文字までの文字数を返します。

#include <string.h>
size_t strspn(const char *s, const char *accept);
size_t strcspn(const char *s, const char *reject);

*sは検索対象文字列を指定します。
*acceptと*rejectは検索する文字のセットを指定します。

戻り値として、文字セットに含まれる又は、含まれない文字までの文字数を返します。該当する文字が無かった場合は、次の値を返します。

  1. strspn関数は、検索対象文字列の文字数(長さ)を返します。
  2. strcspn関数は、0を返します。

プログラム 例

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define SIZE 1024

int main()
{
  FILE             *fp;
  char             path[50];
  char             key_set[11];
  char             buff[SIZE];
  char             *buff_ptr;
  int              key_cnt;
  int              len;

  printf('ファイルのパス名を入力してください ==> ');
  scanf('%s', path);

  if ((fp = fopen(path, 'r')) == NULL) {
    fprintf(stderr, '%sのオープンができませんでした\n', path);
    exit(EXIT_FAILURE);
  }

  printf('検索する文字セットを入力してください(10文字以下) ==> ');
  scanf('%s', key_set);

  key_cnt = 0;
  while(fgets(buff, SIZE, fp) != NULL) {
    buff_ptr = buff;
    while (*buff_ptr) {
      /* 文字セットに無い文字を検索 */
      if ((len = strcspn(buff_ptr, key_set)) == 0) {
        /* 文字セットに有る文字を検索 */
        len = strspn(buff_ptr, key_set);
        key_cnt += len;
        buff_ptr += len;
      }
      else {
        /* 文字セットに無い文字をスキップ */
        buff_ptr += len;
      }
    }
  }
  fclose(fp);

  printf('%sファイルには「%s」のセットが%d個ありました\n',
         path, key_set, key_cnt);

  return EXIT_SUCCESS;
}

例の実行結果

$ cat temp.txt
#include <stdio.h>

int main()
{
  printf('Hello World!!.\n');

  return 0;
}
$
$ ./strspn.exe
ファイルのパス名を入力してください ==> temp.txt
検索する文字セットを入力してください(10文字以下) ==> (){}
temp.txtファイルには「(){}」のセットが6個ありました
$
$ ./strspn.exe
ファイルのパス名を入力してください ==> temp.txt
検索する文字セットを入力してください(10文字以下) ==> WH
temp.txtファイルには「WH」のセットが2個ありました
$